﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using IBS.Model;

namespace IBS.Bll
{
    public static class NumbersGenerator
    {
        private const string BANK_CODE = "739";
        private const string IND_NUMBER = "3012";
        private const string BANK_ID = "54855";

        private static Random random = new Random(DateTime.Now.Millisecond);

        private static String GenerateAccountControlKey(String secondDigits)
        {
            String fullNumber = BANK_CODE + IND_NUMBER + secondDigits;
            int[] weights = {7, 1, 3, 3, 7, 1, 3, 7, 1, 3, 7, 1, 3, 7, 1};
            int sum = 0;
            for (int i = 0; i < weights.Length; i++)
            {
                int digit = weights[i];
                int lastDigit = (digit*weights[i])%10;
                sum += lastDigit;
            }
            int mult = (sum%10)*3;
            return (mult%10).ToString();


        }

        private static String GenerateCardContorlKey(String firstPart)
        {
            int sum_odd = 0;
            int sum_even = 0;
            for (int i = 0; i < firstPart.Length; i++)
            {
                if ((i%2) == 0)
                {
                    int mult = firstPart[i]*2;
                    if (mult >= 10)
                    {
                        mult -= 9;
                    }
                    sum_even += mult;
                }
                else
                {
                    sum_odd = firstPart[i];
                }
            }
            return (10 - ((sum_even + sum_odd)%10)).ToString();
        }

        public static string GenerateAccountNumber()
        {
            var accountNumberGenerator = new StringBuilder();

            var result = Enumerable.Range(1, 8).Select(i=>random.Next(0, 9)).ToList();
            var randomPart = String.Join("", result);
            var controlPart = GenerateAccountControlKey(randomPart);
            accountNumberGenerator.Append(IND_NUMBER)
                .Append(randomPart)
                .Append(controlPart);
            return accountNumberGenerator.ToString();
        }

        public static string GenerateCardNumber(CardType cardType)
        {
            var cardNumberGenerator = new StringBuilder();

            switch (cardType)
            {
                case CardType.VisaClassic:
                    cardNumberGenerator.Append("5");
                    break;
                case CardType.MasterCard:
                    cardNumberGenerator.Append("4");
                    break;
                default:
                    throw new ArgumentOutOfRangeException("cardType");
            }
            cardNumberGenerator.Append(BANK_ID);
            var result = Enumerable.Range(1, 9).Select(i => random.Next(0, 9)).ToList();
            var randomPart = String.Join("", result);
            cardNumberGenerator.Append(randomPart);
            var controlPart = GenerateCardContorlKey(cardNumberGenerator.ToString());
            cardNumberGenerator
                .Append(controlPart);
            return cardNumberGenerator.ToString();
        }

    }
}
